home *** CD-ROM | disk | FTP | other *** search
/ SGI Developer Toolbox 6.1 / SGI Developer Toolbox 6.1 - Disc 4.iso / src / swtools / libdwarf / dwarf_weaks.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-08-02  |  6.7 KB  |  268 lines

  1. #include <stdio.h>
  2. #include "dwarf_incl.h"
  3. #include "dwarf_weaks.h"
  4.  
  5. int
  6. dwarf_get_weaks (
  7.     Dwarf_Debug        dbg,
  8.     Dwarf_Weak        **weaks,
  9.     Dwarf_Signed        *ret_weak_count,
  10.     Dwarf_Error        *error
  11. )
  12. {
  13.     /* Sweeps the complete .debug_weaknames section. */
  14.     Dwarf_Small            *weaknames_ptr;
  15.  
  16.     Dwarf_Word            length;
  17.  
  18.     /* 
  19.         Points to the context for the current set of weak names,
  20.         and contains information to identify the compilation-unit
  21.         that the set refers to.
  22.     */
  23.     Dwarf_Weak_Context        weaknames_context;
  24.  
  25.         /* Version number for the current set of weak names. */
  26.     Dwarf_Half            version;
  27.  
  28.     /* 
  29.         Offset from the start of compilation-unit 
  30.         for the current weak name.
  31.     */
  32.     Dwarf_Off            cu_offset;
  33.  
  34.     /* Counts the number of weak names read. */
  35.     Dwarf_Unsigned        weak_count = 0;
  36.  
  37.     /* Points to the current weak name read. */
  38.     Dwarf_Weak            weak;
  39.  
  40.     /* 
  41.         Used to chain the Dwarf_Weak_s structs for creating
  42.         contiguous list of pointers to the structs.
  43.     */
  44.     Dwarf_Chain            curr_chain, prev_chain, head_chain = NULL;
  45.  
  46.     /* Points to contiguous block of Dwarf_Weak's to be returned. */
  47.     Dwarf_Weak            *ret_weaks;
  48.  
  49.     /* Temporary counter. */
  50.     Dwarf_Unsigned        i;
  51.  
  52.     /* ***** BEGIN CODE ***** */
  53.  
  54.     if (dbg == NULL) 
  55.     {_dwarf_error(NULL, error, DW_DLE_DBG_NULL); return(DW_DLV_ERROR);}
  56.  
  57.     if (dbg->de_debug_weaknames == NULL) {
  58.     return(DW_DLV_NO_ENTRY);
  59.     }
  60.  
  61.     weaknames_ptr = dbg->de_debug_weaknames;
  62.     do {
  63.     weaknames_context = (Dwarf_Weak_Context)
  64.         _dwarf_get_alloc(dbg, DW_DLA_WEAK_CONTEXT, 1);
  65.     if (weaknames_context == NULL) {
  66.         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL); 
  67.         return(DW_DLV_ERROR);
  68.         }
  69.  
  70.     READ_UNALIGNED(length, weaknames_ptr, dbg->de_length_size);
  71.     weaknames_ptr += dbg->de_length_size;
  72.     weaknames_context->wk_length = length;
  73.  
  74.  
  75.     READ_UNALIGNED(version, weaknames_ptr, sizeof(Dwarf_Half));
  76.     weaknames_ptr += sizeof(Dwarf_Half);
  77.     if (version != CURRENT_VERSION_STAMP) {
  78.         _dwarf_error(dbg, error, DW_DLE_DEBUG_WEAKNAMES_VERSION_ERROR);
  79.         return(DW_DLV_ERROR);
  80.     }
  81.  
  82.     READ_UNALIGNED(weaknames_context->wk_info_offset, weaknames_ptr, 
  83.         dbg->de_length_size);
  84.     weaknames_ptr += dbg->de_length_size;
  85.     
  86.         /* 
  87.         Add the length of the cu_header to point to the
  88.         DW_TAG_compile_unit die.
  89.         */
  90.     weaknames_context->wk_info_offset +=
  91.         dbg->de_length_size +    /* Size of cu length field. */
  92.         sizeof(Dwarf_Half) +    /* Size of version stamp field. */
  93.         dbg->de_length_size +    /* Size of abbrev offset field. */
  94.         sizeof(Dwarf_Small);    /* Size of address size field. */
  95.  
  96.     READ_UNALIGNED(weaknames_context->wk_info_length, weaknames_ptr, 
  97.         dbg->de_length_size);
  98.     weaknames_ptr += dbg->de_length_size;
  99.  
  100.     if (weaknames_ptr > dbg->de_debug_weaknames +
  101.         dbg->de_debug_weaknames_size) {
  102.         _dwarf_error(dbg, error, DW_DLE_DEBUG_WEAKNAMES_LENGTH_BAD);
  103.         return(DW_DLV_ERROR);
  104.     }
  105.  
  106.     READ_UNALIGNED(cu_offset, weaknames_ptr, dbg->de_length_size);
  107.     weaknames_ptr += dbg->de_length_size;
  108.  
  109.     while (cu_offset != 0) {
  110.  
  111.             weak = (Dwarf_Weak)_dwarf_get_alloc(dbg, DW_DLA_WEAK, 1);
  112.         if (weak == NULL) {
  113.         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL); 
  114.         return(DW_DLV_ERROR);
  115.         }
  116.         weak_count++;
  117.  
  118.         weak->we_context = weaknames_context;
  119.  
  120.         /* Subtract length of CU header to adjust offsets. */
  121.             weak->we_cu_offset = cu_offset -
  122.         dbg->de_length_size -    /* Size of CU length field. */
  123.         sizeof(Dwarf_Half) -    /* Size of version stamp field. */
  124.         dbg->de_length_size -    /* Size of abbrev offset field. */
  125.         sizeof(Dwarf_Small);    /* Size of address size field. */
  126.  
  127.         weak->we_name = weaknames_ptr;
  128.         weaknames_ptr = weaknames_ptr + strlen(weaknames_ptr) + 1;
  129.  
  130.         READ_UNALIGNED(cu_offset, weaknames_ptr, dbg->de_length_size);
  131.         weaknames_ptr += dbg->de_length_size;
  132.  
  133.         if (weaknames_ptr > dbg->de_debug_weaknames + 
  134.         dbg->de_debug_weaknames_size) {
  135.         _dwarf_error(dbg, error, DW_DLE_DEBUG_WEAKNAMES_LENGTH_BAD);
  136.         return(DW_DLV_ERROR);
  137.         }
  138.  
  139.         curr_chain = (Dwarf_Chain)_dwarf_get_alloc(dbg, DW_DLA_CHAIN, 1);
  140.         if (curr_chain == NULL) {
  141.         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
  142.         return(DW_DLV_ERROR);
  143.         }
  144.  
  145.         /* Put current weak name on singly_linked list. */
  146.         curr_chain->ch_item = (Dwarf_Weak)weak;
  147.         if (head_chain == NULL)
  148.         head_chain = prev_chain = curr_chain;
  149.         else {
  150.         prev_chain->ch_next = curr_chain;
  151.         prev_chain = curr_chain;
  152.         }
  153.     }
  154.  
  155.     } while (weaknames_ptr < 
  156.     dbg->de_debug_weaknames + dbg->de_debug_weaknames_size);
  157.     
  158.     /* Points to contiguous block of Dwarf_Weak's. */
  159.     ret_weaks = (Dwarf_Weak *)
  160.     _dwarf_get_alloc(dbg, DW_DLA_LIST, weak_count);
  161.     if (ret_weaks == NULL) {
  162.     _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL); 
  163.     return(DW_DLV_ERROR);
  164.     }
  165.  
  166.     /* 
  167.         Store pointers to Dwarf_Weak_s structs in
  168.         contiguous block, and deallocate the chain.
  169.     */
  170.     curr_chain = head_chain;
  171.     for (i = 0; i < weak_count; i++) {
  172.     *(ret_weaks + i) = curr_chain->ch_item;
  173.     prev_chain = curr_chain;
  174.     curr_chain = curr_chain->ch_next;
  175.     dwarf_dealloc(dbg, prev_chain, DW_DLA_CHAIN);
  176.     }
  177.  
  178.     *weaks = ret_weaks;
  179.     *ret_weak_count = (weak_count);
  180.     return DW_DLV_OK;
  181. }
  182.  
  183.  
  184. int
  185. dwarf_weakname (
  186.     Dwarf_Weak        weak,
  187.     char **         ret_name,
  188.     Dwarf_Error        *error
  189. )
  190. {
  191.     if (weak == NULL) {
  192.     _dwarf_error(NULL, error, DW_DLE_WEAK_NULL); 
  193.     return(DW_DLV_ERROR);
  194.     }
  195.  
  196.     *ret_name = (weak->we_name);
  197.     return DW_DLV_OK;
  198. }
  199.  
  200.  
  201. int
  202. dwarf_weak_die_offset (
  203.     Dwarf_Weak        weak,
  204.     Dwarf_Off          *weak_off,
  205.     Dwarf_Error        *error
  206. )
  207. {
  208.     if (weak == NULL) 
  209.     {_dwarf_error(NULL, error, DW_DLE_WEAK_NULL); 
  210.     return(DW_DLV_ERROR);}
  211.  
  212.     if (weak->we_context == NULL) {
  213.     _dwarf_error(NULL, error, DW_DLE_WEAK_CONTEXT_NULL);
  214.     return(DW_DLV_ERROR);
  215.     }
  216.  
  217.     *weak_off = (weak->we_cu_offset + weak->we_context->wk_info_offset);
  218.     return DW_DLV_OK;
  219. }
  220.  
  221.  
  222. int
  223. dwarf_weak_cu_offset (
  224.     Dwarf_Weak        weak,
  225.     Dwarf_Off          *weak_off,
  226.     Dwarf_Error        *error
  227. )
  228. {
  229.     if (weak == NULL)
  230.     {_dwarf_error(NULL, error, DW_DLE_WEAK_NULL); return(DW_DLV_ERROR);}
  231.  
  232.     if (weak->we_context == NULL) {
  233.     _dwarf_error(NULL, error, DW_DLE_WEAK_CONTEXT_NULL);
  234.     return(DW_DLV_ERROR);
  235.     }
  236.  
  237.     *weak_off = (weak->we_context->wk_info_offset);
  238.     return DW_DLV_OK;
  239. }
  240.  
  241.  
  242. int
  243. dwarf_weak_name_offsets (
  244.     Dwarf_Weak        weak,
  245.     char    **          weak_name,
  246.     Dwarf_Off        *die_offset,
  247.     Dwarf_Off        *cu_offset,
  248.     Dwarf_Error        *error
  249. )
  250. {
  251.     if (weak == NULL)
  252.     {_dwarf_error(NULL, error, DW_DLE_WEAK_NULL); return(DW_DLV_ERROR);}
  253.  
  254.     if (weak->we_context == NULL) 
  255.     {_dwarf_error(NULL, error, DW_DLE_WEAK_CONTEXT_NULL); 
  256.     return(DW_DLV_ERROR);}
  257.  
  258.     if (die_offset != NULL)
  259.     *die_offset = weak->we_cu_offset + 
  260.         weak->we_context->wk_info_offset;
  261.  
  262.     if (cu_offset != NULL)
  263.     *cu_offset = weak->we_context->wk_info_offset;
  264.  
  265.     *weak_name = (weak->we_name);
  266.     return DW_DLV_OK;
  267. }
  268.